/**
 * Copyright &copy; 2012-2016 <a href="https://istep.lczyfz.com">Istep</a> All rights reserved.
 */
package com.lczyfz.istep.modules.scene.web;

import com.lczyfz.istep.common.config.Global;
import com.lczyfz.istep.common.constants.DelFlag;
import com.lczyfz.istep.common.persistence.Page;
import com.lczyfz.istep.common.utils.JsonModel;
import com.lczyfz.istep.common.utils.StringUtils;
import com.lczyfz.istep.common.web.BaseController;
import com.lczyfz.istep.modules.openstack.api.glance.impl.ImageDataImpl;
import com.lczyfz.istep.modules.openstack.api.glance.impl.ImagesImpl;
import com.lczyfz.istep.modules.openstack.api.glance.interfaces.Images;
import com.lczyfz.istep.modules.openstack.api.glance.model.Image;
import com.lczyfz.istep.modules.openstack.api.keystone.model.OsUser;
import com.lczyfz.istep.modules.openstack.api.nova.impl.HypervisorImpl;
import com.lczyfz.istep.modules.openstack.api.nova.impl.VirtualMachineImpl;
import com.lczyfz.istep.modules.openstack.api.nova.impl.serveraction.ServerActionsImpl;
import com.lczyfz.istep.modules.openstack.api.nova.model.Hypervisor;
import com.lczyfz.istep.modules.resource.service.ResourceFileService;
import com.lczyfz.istep.modules.scene.entity.*;
import com.lczyfz.istep.modules.scene.service.*;
import com.lczyfz.istep.modules.sys.service.ScheduleJobService;
import com.lczyfz.istep.modules.sys.service.SystemService;
import org.apache.shiro.authz.annotation.RequiresPermissions;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Controller;
import org.springframework.ui.Model;
import org.springframework.web.bind.annotation.*;
import org.springframework.web.multipart.MultipartFile;
import org.springframework.web.multipart.MultipartHttpServletRequest;
import org.springframework.web.multipart.commons.CommonsMultipartResolver;
import org.springframework.web.servlet.mvc.support.RedirectAttributes;

import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import java.io.IOException;
import java.math.BigDecimal;
import java.math.RoundingMode;
import java.util.ArrayList;
import java.util.Iterator;
import java.util.List;

/**
 * 虚拟机模板管理Controller
 * @author dh
 * @version 2017-04-06
 */
@Controller
@RequestMapping(value = "${adminPath}/scene/sceneVmTemplate")
public class SceneVmTemplateController extends BaseController {

	@Autowired
	private SceneVmTemplateService sceneVmTemplateService;
	@Autowired
	private SystemService systemService;
	@Autowired
	private SceneVmTypeService sceneVmTypeService;
	@Autowired
	private SceneNetworkService sceneNetworkService;
	@Autowired
	private ResourceFileService resourceFileService;
	@Autowired
	private ScenePortService scenePortService;
	@Autowired
	private SceneSecurityGroupService sceneSecurityGroupService;
	@Autowired
	private SceneEnvironmentInstanceService sceneEnvironmentInstanceService;
	@Autowired
	private SceneCtfEnvironmentInstanceService sceneCtfEnvironmentInstanceService;
	@Autowired
	private ScheduleJobService scheduleJobService;
	private static String fileid;

	@ModelAttribute
	public SceneVmTemplate get(@RequestParam(required=false) String id) {
		SceneVmTemplate entity = null;
		if (StringUtils.isNotBlank(id)){
			entity = sceneVmTemplateService.get(id);
		}
		if (entity == null){
			entity = new SceneVmTemplate();
		}
		return entity;
	}
	
	@RequiresPermissions("scene:sceneVmTemplate:view")
	@RequestMapping(value = {"list", ""})
	public String list(SceneVmTemplate sceneVmTemplate, HttpServletRequest request, HttpServletResponse response, Model model) {
		if(systemService.isSuperAdmin())
		{
			model.addAttribute("isSuperAdmin", "true");
		}
		else
		{
			model.addAttribute("isSuperAdmin", "false");
		}

		Page<SceneVmTemplate> page = sceneVmTemplateService.findPage(new Page<SceneVmTemplate>(request, response), sceneVmTemplate);
		model.addAttribute("page", page);
		return "modules/scene/sceneVmTemplateList";
	}

	@RequiresPermissions("scene:sceneVmTemplate:view")
	@RequestMapping(value = "form")
	public String form(SceneVmTemplate sceneVmTemplate, Model model) {
		if(systemService.isSuperAdmin())
		{
			model.addAttribute("isSuperAdmin", "true");
		}else
			model.addAttribute("isSuperAdmin", "false");
		//获取镜像列表
		List<Image> imageList=new ArrayList<>();
		try{
			ImagesImpl imageImpl = new ImagesImpl();
			imageList= imageImpl.getImages();
		}catch (Exception e){
			logger.debug("获取虚拟机镜像失败！");
           e.printStackTrace();
		}
		logger.debug("imageList.size()===" + imageList.size());

		model.addAttribute("imageList", imageList);
		//获取云主机列表
		List<SceneVmType> vmTypeList=sceneVmTypeService.findList(new SceneVmType());
		model.addAttribute("vmTypeList", vmTypeList);
		//获取网络列表
		List<SceneNetwork> networkList= sceneNetworkService.findList(new SceneNetwork());
		model.addAttribute("networkList", networkList);
		//获取端口列表
		List<ScenePort> portList= scenePortService.findList(new ScenePort());
		model.addAttribute("portList", portList);

		//获取安全组列表
		List<SceneSecurityGroup> securityGroupList= sceneSecurityGroupService.findList(new SceneSecurityGroup());
		model.addAttribute("securityGroupList", securityGroupList);

		//
//		List<SceneNetwork> snList;
//		if(sceneVmTemplate!=null) {
//			snList = sceneNetworkService.findVmNetworkList(sceneVmTemplate);
//		}
		model.addAttribute("sceneVmTemplate", sceneVmTemplate);
		return "modules/scene/sceneVmTemplateForm";
//		return "modules/scene/sceneEnvironmentTopology";

	}

	@RequiresPermissions("scene:sceneVmTemplate:edit")
	@RequestMapping(value = "save")
	public String save(SceneVmTemplate sceneVmTemplate,String imageId, Model model, RedirectAttributes redirectAttributes,String networkIds,String portIds,String sgIds) {
		if (!beanValidator(model, sceneVmTemplate)){
			return form(sceneVmTemplate, model);
		}
		logger.debug("imageId===" + imageId+" "+sceneVmTemplate.getImageName());

		if(sceneVmTemplate.getImageRef().equals("")&&!imageId.equals(""))
		{
			sceneVmTemplate.setImageRef(imageId);
		}
		logger.debug("networkIds===" + networkIds+" "+portIds);
		logger.debug("sceneVmTemplate.getName()===" + sceneVmTemplate.getName());
		logger.debug("sceneVmTemplate.getImageref()===" + sceneVmTemplate.getImageRef());
		SceneVmTemplate temp=sceneVmTemplateService.findVmTemplateByName(sceneVmTemplate.getName(),DelFlag.DEL_FLAG_NORMAL);
		if(sceneVmTemplateService.get(sceneVmTemplate)==null)
		{
			if(temp!=null)
			{
				addMessage(redirectAttributes, "保存虚拟机模板失败，该模板已存在");
				return "redirect:"+Global.getAdminPath()+"/scene/sceneVmTemplate/?repage";
			}
		}else {
			if(temp!=null&&!temp.getId().equals(sceneVmTemplate.getId()))
			{
				addMessage(redirectAttributes, "修改虚拟机模板失败，该模板已存在");
				return "redirect:"+Global.getAdminPath()+"/scene/sceneVmTemplate/?repage";
			}
		}

		sceneVmTemplateService.save(sceneVmTemplate);

		addMessage(redirectAttributes, "保存虚拟机模板成功");
		return "redirect:"+Global.getAdminPath()+"/scene/sceneVmTemplate/?repage";
	}
	
	@RequiresPermissions("scene:sceneVmTemplate:edit")
	@RequestMapping(value = "delete")
	public String delete(SceneVmTemplate sceneVmTemplate, RedirectAttributes redirectAttributes) {
//		try{
//			VirtualMachineImpl nova = new VirtualMachineImpl();
//			nova.deleteServer(sceneVmTemplate.getId());
//
//			sceneVmTemplateService.delete(sceneVmTemplate);
//			addMessage(redirectAttributes, "删除虚拟机模板成功");
//		}catch (RuntimeException e){
//			addMessage(redirectAttributes, "删除虚拟机模板失败");
//
//		}
		sceneVmTemplateService.delete(sceneVmTemplate);
		addMessage(redirectAttributes, "删除虚拟机模板成功");
		return "redirect:"+Global.getAdminPath()+"/scene/sceneVmTemplate/?repage";
	}
	/**
	 * 上传镜像
	 *
	 * @param request
	 * @param response
	 * @return
	 */
	@ResponseBody
	@RequestMapping(value = "imageUpload", method = RequestMethod.POST)
	public JsonModel imageUpload(HttpServletRequest request, HttpServletResponse response) {
		logger.debug("上传===imageUpload");

		JsonModel jsonModel = new JsonModel();
		CommonsMultipartResolver multipartResolver = new CommonsMultipartResolver(
				request.getSession().getServletContext());
		if (multipartResolver.isMultipart(request)) {
			//将request变成多部分request
			MultipartHttpServletRequest multiRequest = (MultipartHttpServletRequest) request;
			//获取multiRequest 中所有的文件名
			Iterator iter = multiRequest.getFileNames();
			while (iter.hasNext()) {
				//一次遍历所有文件
				MultipartFile file = multiRequest.getFile(iter.next().toString());
				if (file != null) {
					logger.debug("上传镜像===123");
					//得到上传的文件名称
					String fileName = file.getOriginalFilename();
					//得到后缀
					String suffix = fileName.substring(fileName.lastIndexOf(".") + 1, fileName.length());
					Images images = new ImagesImpl();
					Image image = new Image();
					image.setName(fileName);
					image.setDiskFormat(suffix);
					image.setvisibility("public");
					Image newimage = images.creatImage(image);

					ImageDataImpl impl = new ImageDataImpl();
					try {
						impl.uploadImage(newimage.getId(), file.getInputStream());
						logger.debug("上传镜像成功===");
						List<String> fileInfo=new ArrayList<>();
						fileInfo.add(fileName);
						fileInfo.add(newimage.getId());
						jsonModel.setSuccess(true);
						jsonModel.setDataObj(fileInfo);
						logger.debug("上传镜像成功===" + fileInfo.get(0)+" "+fileInfo.get(1));

						return jsonModel;
					} catch (IOException e) {
						e.printStackTrace();
						jsonModel.setSuccess(false);
						return jsonModel;
					}

				}
			}
		}
		jsonModel.setSuccess(false);
		return jsonModel;

	}

	/**
	 * 虚拟机监控
	 * @param model
	 * @return
	 */
	@RequestMapping(value = "hypervisorSummary")
	public String hypervisorSummary(Model model) {
		Hypervisor hypervisorSummary=new Hypervisor();
		logger.debug("dingh===虚拟机监控");

		try{
			HypervisorImpl hypervisordemo = new HypervisorImpl();
			hypervisorSummary = hypervisordemo.getHypervisorStatistics();
		}catch (RuntimeException e){

		}

		logger.debug("dingh===虚拟机监控=" + hypervisorSummary.getVcpus() + " " + hypervisorSummary.getVcpusUsed());
		BigDecimal bigDecimal=null;
		if(hypervisorSummary.getMemoryMb()!=null)
		{
			bigDecimal=new BigDecimal(hypervisorSummary.getMemoryMb()).divide(new BigDecimal("1024"), 1, RoundingMode.HALF_DOWN);
			hypervisorSummary.setMemoryMb(bigDecimal.toString());
		}
		if(hypervisorSummary.getMemoryMbUsed()!=null)
		{
			bigDecimal=new BigDecimal(hypervisorSummary.getMemoryMbUsed()).divide(new BigDecimal("1024"), 1, RoundingMode.HALF_DOWN);
			hypervisorSummary.setMemoryMbUsed(bigDecimal.toString());
		}

		model.addAttribute("hypervisorSummary", hypervisorSummary);
		return "modules/scene/sceneOsHypervisor";

	}
	/**
	 * 用户监控
	 * @param model
	 * @return
	 */
	@RequestMapping(value = "userMonitor")
	public String userMonitor(Model model,String userName,String email) {
		logger.debug("dingh===用户监控");
		OsUser user=new OsUser();
		user.setUserName("admin");
		user.setIsAvailable("是");
		List<OsUser> userList=new ArrayList<>();

		logger.debug("dingh===userName="+userName);
		logger.debug("dingh===email="+email);

		if(email==null||"".equals(email))
		{
			if(userName!=null)
			{
				logger.debug("dingh===userName="+userName);

				if(userName.equals("admin")||userName.contains("admin")||"admin".contains(userName))
				{
					userList.add(user);
				}
			}else {
				userList.add(user);
			}
		}

		model.addAttribute("userList", userList);
		model.addAttribute("userName", userName);
		model.addAttribute("email", email);

		return "modules/scene/sceneOsUserMonitor";

	}
	/**
	 * 实验环境实例监控
	 * @param model
	 * @return
	 */
	@RequestMapping(value = "instanceMonitor")
	public String instanceMonitor(Model model,SceneEnvironmentInstance sceneEnvironmentInstance,HttpServletRequest request, HttpServletResponse response) {
		logger.debug("dingh===实验环境实例监控");
		logger.debug("dingh===实验环境实例监控="+sceneEnvironmentInstance.getBeginEndDate());
		logger.debug("dingh===实验环境实例监控=" + sceneEnvironmentInstance.getEndEndDate());
		logger.debug("dingh===实验环境实例监控=" + sceneEnvironmentInstance.getCreateBy());

		Page<SceneEnvironmentInstance> page = sceneVmTemplateService.findVmMonitorPage(new Page<SceneEnvironmentInstance>(request, response), sceneEnvironmentInstance);

		model.addAttribute("page", page);


		return "modules/scene/sceneOsInstanceMonitor";

	}
	/**
	 * 查看资源占用
	 */
	@ResponseBody
	@RequestMapping(value = "viewResourceDetail")
	public SceneVmTemplate viewResourceDetail(@RequestParam(required = false) String ids) {

		SceneVmTemplate sceneVmTemplate=sceneVmTemplateService.viewResourceDetail(ids);
		return sceneVmTemplate;
	}
	/**
	 * 查看ctf资源占用
	 */
	@ResponseBody
	@RequestMapping(value = "viewCtfResourceDetail")
	public SceneVmTemplate viewCtfResourceDetail(@RequestParam(required = false) String ids) {

		SceneVmTemplate sceneVmTemplate=sceneVmTemplateService.viewCtfResourceDetail(ids);
		return sceneVmTemplate;
	}
	/**
	 * 销毁实例
	 * @param instanceId
	 * @param instanceId
	 * @return
	 */
	@RequestMapping(value = "deleteInstance")
	public String deleteInstance(@RequestParam(required = false) String instanceId,@RequestParam(required = false) String vmTemplateId,@RequestParam(required = false) String type, RedirectAttributes redirectAttributes) throws RuntimeException,Exception{
		logger.debug("dingh===endExperiment=" + instanceId+" "+vmTemplateId+type);


		VirtualMachineImpl nova = new VirtualMachineImpl();
		nova.deleteServer(vmTemplateId);

		sceneVmTemplateService.vmMonitorDelete(instanceId, vmTemplateId);
		addMessage(redirectAttributes, "虚拟机成功销毁");

		if(type.equals("0"))
		{
			return "redirect:"+Global.getAdminPath()+"/scene/sceneVmTemplate/instanceMonitor?repage";
		}else {
			return "redirect:"+Global.getAdminPath()+"/scene/sceneVmTemplate/ctfInstanceMonitor?repage";
		}


	}

	/**
	 * ctf实验环境实例监控
	 * @param model
	 * @return
	 */
	@RequestMapping(value = "ctfInstanceMonitor")
	public String ctfInstanceMonitor(Model model,SceneCtfEnvironmentInstance sceneCtfEnvironmentInstance,HttpServletRequest request, HttpServletResponse response) {
		logger.debug("dingh===ctf实验环境实例监控");

		Page<SceneCtfEnvironmentInstance> page = sceneVmTemplateService.findCtfVmMonitorPage(new Page<SceneCtfEnvironmentInstance>(request, response), sceneCtfEnvironmentInstance);

		model.addAttribute("page", page);
		return "modules/scene/sceneOsCtfInstanceMonitor";

	}
	/**
	 * 重启服务器（虚拟机）
	 * @param id
	 * @return
	 */
	@RequestMapping(value = "rebootServer")
	public String rebootServer(@RequestParam(required = false) String id,@RequestParam(required = false) String type, RedirectAttributes redirectAttributes) throws Exception{
		logger.debug("dingh===rebootServer=" + id+" "+ type);
		ServerActionsImpl ServerActionsdemo = new ServerActionsImpl();
		ServerActionsdemo.RebootServer(id);
		addMessage(redirectAttributes, "虚拟机重启成功");
		if(type.equals("0"))
		{
			return "redirect:"+Global.getAdminPath()+"/scene/sceneVmTemplate/instanceMonitor?repage";
		}else {
			return "redirect:"+Global.getAdminPath()+"/scene/sceneVmTemplate/ctfInstanceMonitor?repage";
		}

	}

	/**
	 * 上传镜像文件
	 *
	 * @param file
	 * @param response
	 * @return
	 */
	@ResponseBody
	@RequestMapping(value = "upload", method = RequestMethod.POST)
	public String uploadFile(@RequestParam MultipartFile file, HttpServletResponse response) {

		logger.debug("上传镜像===123");
		if(file!=null&&!file.isEmpty())
		{
			logger.debug("上传镜像===123");
			//得到上传的文件名称
			String fileName = file.getOriginalFilename();
			//得到后缀
			String suffix = fileName.substring(fileName.lastIndexOf(".") + 1, fileName.length());
			Images images = new ImagesImpl();
			Image image = new Image();
			image.setName(fileName);
			image.setDiskFormat(suffix);
			image.setvisibility("public");
			Image newimage = images.creatImage(image);

			ImageDataImpl impl = new ImageDataImpl();
			try {
				impl.uploadImage(newimage.getId(), file.getInputStream());
				logger.debug("上传镜像成功===" + newimage.getId());
				fileid=newimage.getId();
			} catch (IOException e) {
				e.printStackTrace();
			}
		}
//		fileid="123";
		if(fileid==null||fileid.equals(""))
		{
			fileid="";
		}
		try {
			response.getWriter().write(fileid);  //ids换成后台获取到的文件id
		} catch (IOException e) {
			e.printStackTrace();
		}
		return null;

	}
	/**
	 * @param
	 * @return
	 * @author dingh
	 * @date 2017/2/25
	 * @des ajax删除已上传镜像
	 */
	@ResponseBody
	@RequestMapping(value = "uploadFileDelete")
	public JsonModel uploadFileDelete(String uploadFileId) {
		JsonModel jsonModel = new JsonModel();
		logger.debug("uploadFileId:" + uploadFileId);
		try{
			Images images = new ImagesImpl();
			images.deleteImage(uploadFileId);
			jsonModel.setSuccess(true);
			String successMsg = "镜像删除成功。";
			jsonModel.setMsg(successMsg);
			jsonModel.setDataObj(uploadFileId);
		}
		catch(Exception e)
		{
			e.printStackTrace();
			jsonModel.setSuccess(false);
			String successMsg = "镜像删除失败。";
			jsonModel.setMsg(successMsg);
			jsonModel.setDataObj(uploadFileId);
		}

		jsonModel.setSuccess(false);
		String successMsg = "镜像删除失败。";
		jsonModel.setMsg(successMsg);
		jsonModel.setDataObj(uploadFileId);
//		jsonModel.setSuccess(true);
//		String successMsg = "镜像删除成功。";
//		jsonModel.setMsg(successMsg);
//		jsonModel.setDataObj(uploadFileId);
		return jsonModel;
	}

}